package com.hrm.common.service;

import org.springframework.data.jpa.domain.Specification;
import org.springframework.util.StringUtils;

import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

public class BaseService<T> {

    /**
     * 根据companyId查询
     * 需要导入jpa依赖
     * @return
     */
    protected Specification<T> setSpec(String companyId){
        /**
         * 用于构造查询条件
         *  root: 包含对象属性
         *  cq：高级查询
         *  cb：构造查询条件
         *      拼接得到companyId=root.get("companyId").as(String.class)
         */
        return new Specification<T>() {
            @Override
            public Predicate toPredicate(Root<T> root, CriteriaQuery<?> cq, CriteriaBuilder cb) {
                //根据属性去查找
                return cb.equal(root.get("companyId").as(String.class),companyId);
            }
        };
    }

    /**
     * 根据companyId、departmentId、hasDept查询
     * 需要导入jpa依赖
     * @return
     */
    protected Specification<T> setSpec4User(Map<String, Object> map){
        //1、需要查询条件
        return new Specification<T>() {
            @Override
            public Predicate toPredicate(Root<T> root, CriteriaQuery<?> cq, CriteriaBuilder cb) {
                List<Predicate> list = new ArrayList<>();
                //companyId不为空字符串或null
                if (!StringUtils.isEmpty(map.get("companyId"))) {
                    list.add(cb.equal(root.get("companyId").as(String.class), map.get("companyId")));
                }
                //departmentId不为空字符串或null
                if (!StringUtils.isEmpty(map.get("departmentId"))) {
                    list.add(cb.equal(root.get("departmentId").as(String.class), map.get("departmentId")));
                }
                //hasDept为0或null表示为分配部门，否则1为分配
                if (StringUtils.isEmpty(map.get("hasDept")) || "0".equals(map.get("hasDept"))) {
                    list.add(cb.isNull(root.get("departmentId")));
                } else {
                    list.add(cb.isNotNull(root.get("departmentId")));
                }
                return cb.and(list.toArray(new Predicate[list.size()]));
            }
        };
    }

    /**
     * 根据parentId、enVisible、type查询
     * 需要导入jpa依赖
     * @return
     */
    protected Specification<T> setSpec4Permission(Map<String, Object> map){
        return new Specification<T>() {
            @Override
            public Predicate toPredicate(Root<T> root, CriteriaQuery<?> cq, CriteriaBuilder cb) {
                ArrayList<Object> list = new ArrayList<>();
                //父id查询
                if (!StringUtils.isEmpty(map.get("parentId"))) {
                    list.add(cb.equal(root.get("parentId").as(String.class), (String) map.get("parentId")));
                }
                //可见性查询
                if (!StringUtils.isEmpty(map.get("enVisible"))) {
                    list.add(cb.equal(root.get("enVisible").as(String.class), (String) map.get("enVisible")));
                }
                //类型查询
                if (!StringUtils.isEmpty(map.get("type"))) {
                    String type = (String) map.get("type");
                    CriteriaBuilder.In<Object> in = cb.in(root.get("type"));
                    if ("0".equals(type)) {
                        in.value(1).value(2);
                    } else {
                        in.value(Integer.parseInt(type));
                    }
                    list.add(in); //in查询
                }
                return cb.and(list.toArray(new Predicate[list.size()])); //and查询
            }
        };
    }
}
